#include "SubsystemDisguiseBehavior.h"
#include "GameSingleton.h"
#include "Subsystems/SubsystemTerrain.h"

#include "Blocks/GraniteBlock.h"   // 花岗岩，伪装煤矿，铜矿
#include "Blocks/BasaltBlock.h"    // 玄武岩，伪装其它矿物
#include "Blocks/SandstoneBlock.h" // 砂岩，伪装硝石

#include "Blocks/CoalOreBlock.h"
#include "Blocks/CopperOreBlock.h"

#include "Blocks/SaltpeterOreBlock.h"

#include "Blocks/IronOreBlock.h"
#include "Blocks/SulphurOreBlock.h"
#include "Blocks/DiamondOreBlock.h"
#include "Blocks/GermaniumOreBlock.h"


namespace AntiMineralTrace
{
    SubsystemDisguiseBehavior::SubsystemDisguiseBehavior()
    {
        m_handleBlocks.push_back(GraniteBlock::Index());
        m_handleBlocks.push_back(BasaltBlock::Index());
        m_handleBlocks.push_back(SandstoneBlock::Index());
    }

    void SubsystemDisguiseBehavior::onNeighborBlockChanged(int32_t x, int32_t y, int32_t z, int32_t neighborX, int32_t neighborY, int32_t neighborZ)
    {
        int32_t blockValue = m_terrain->getCellValue(x, y, z);
        int32_t blockData = Terrain::ExtractData(blockValue);
        int32_t specialValue = GetSpecial(blockData);
        if (specialValue > 0)
        {
            int32_t blockContents = Terrain::ExtractContents(blockValue);
            switch (blockContents)
            {
            case GraniteBlock::Index():
                if (specialValue == Granite_CoalOreBlock)
                {
                    m_terrain->changeCell(x, y, z, CoalOreBlock::Index());
                }
                else if (specialValue == Granite_CopperOreBlock)
                {
                    m_terrain->changeCell(x, y, z, CopperOreBlock::Index());
                }
                break;
            case BasaltBlock::Index():
                switch (specialValue)
                {
                case Basalt_IronOreBlock:
                    m_terrain->changeCell(x, y, z, IronOreBlock::Index());
                    break;
                case Basalt_SulphurOreBlock:
                    m_terrain->changeCell(x, y, z, SulphurOreBlock::Index());
                    break;
                case Basalt_DiamondOreBlock:
                    m_terrain->changeCell(x, y, z, DiamondOreBlock::Index());
                    break;
                case Basalt_GermaniumOreBlock:
                    m_terrain->changeCell(x, y, z, GermaniumOreBlock::Index());
                    break;
                }
                break;
            case SandstoneBlock::Index():
                m_terrain->changeCell(x, y, z, SaltpeterOreBlock::Index());
                break;
            }
        }
    }

    void SubsystemDisguiseBehavior::load(const nlohmann::json &json)
    {
        m_terrain = GameSingleton::singletonPtr->getSingleton<SubsystemTerrain>();
    }

    static const std::string subsystemName = "DisguiseBehavior";
    const std::string &SubsystemDisguiseBehavior::getName() const
    {
        return subsystemName;
    }
}